<?php

class bozBom{

    use bozBomBase1; 
    use bozBomMotor; 

    //static $xxx = DIR_PR . "/xxx"; 

    // 显示:Actiton + Rem(自制/采购 )
    static function vActrem($row, $r3){
        //
        $sum = $r3['cnt'] * $row['数量']; 
        $tip = empty($r3['tip']) ? '' : 'tip';
        $ekid = (!empty($r3['kid']) && !empty($row['kid']) && strstr($r3['kid'],$row['kid'])) ? $r3['kid'] : '';
        $act = "openEditm('".($ekid ? 'upd' : 'edit')."',this,'$ekid')"; //dump($r3);
        if(!empty($row['act']) && $row['act']!='add'){ $act=''; }
        //
        $rem = $r3['备注'];
        $flgN = strstr($rem,'请添加物料') || strstr($rem,'人工确认') || strstr($rem,'客供电机');
        $matCfgs = bozErp::bzcfg('Share', 'matActs'); 
        if(strlen($r3['编码'])<5 || !isset($r3['库存数量']) || $flgN){
            // 请添加物料!!,人工确认!!,客供电机!! 等错误信息
        }elseif(strpos($matCfgs['etMotor'],substr($r3['编码'],0,1))){ // 电机采购
            $rem = str_replace("电机架", '', $rem);
            if(!strstr($rem,'自制') && !strstr($rem,'采购')){ $rem .= ($rem?'/':'') . '采购'; }
        }elseif($r3['库存数量']>=$sum){ // 库存>用量:去掉之前的`采购/自制`标记
            $rem = str_replace(['/自制','自制','/采购','采购'], '', $rem); 
        }elseif($r3['库存数量']<$sum){ 
            $ch2 = substr($r3['编码'],0,2); $ext = '采购';
            if(strpos($matCfgs['sfMade'],$ch2)){ $ext = '自制'; }
            if(strpos($matCfgs['ohMade'],$ch2)){ $ext = '外协'; }
            if(!strstr($rem,'自制') && !strstr($rem,'采购') && !strstr($rem,'外协')){ $rem .= ($rem?'/':'') . $ext; }
        }else{
            //echo $rem;
        }
        //
        return ['sum'=>$sum, 'act'=>$act, 'rem'=>$rem];
    }

    # =================================================================

    // 从db查询一行物料 
    static function itmDb($code, $name, $whr=''){
        $whr = $whr ? $whr : "`编码`='$code'"; 
        $rdb = data('store_main', $whr, '1', '' , 'erp');
        if(empty($rdb)){ 
            $tb = ['code'=>'编码', 'spec'=>'规格图号']; $spec = '';
            foreach($tb as $tk=>$tf){
                preg_match("/\`$tf\`([^\']{1,8})\'([^\']+)\'/i", $whr, $it); 
                if(!empty($it[2])){ $$tk = $it[2]; }
            }
            $rdb = ['编码'=>$code,'名称'=>$name,'priceMain'=>0,'priceAdd'=>0,'规格图号'=>$spec,'备注'=>'请添加物料!!','tip'=>1]; //dump($rdb);
        } 
        $rdb['单价'] = $rdb['priceMain'];
        return $rdb;
    }
    // 修正一行物料资料
    static function itmFix(&$itm, $no=0, $cfg=[]){
        $itm['no'] = $no;
        // TODO: 备注:采购/库位/库存
        $tb = ['规格图号'=>'---','材料'=>'-','表面处理'=>'-','单位'=>'PCS','cnt'=>1,'单价'=>0]; // '备注'=>'---',
        foreach($tb as $tk=>$tv){ 
            if(empty($itm[$tk])){ 
                $itm[$tk] = empty($cfg[$tk]) ? $tv : $cfg[$tk]; 
            } 
        } 
        $rem = empty($itm['备注']) ? (empty($cfg['rem'])?'':$cfg['rem']) : $itm['备注']; // cfg:注意开窗 + 请添加物料!!
        $rem .= empty($itm['仓位号']) ? '' : ($rem?'/':'') . $itm['仓位号']; // A-55-50(采购)
        $itm['备注'] = $rem;
        return $itm; 
    }

    // 按区间BL忽略(skip) // small/large/bet/intb:B/L
    static function skipBL($cfg, $vdefs){
        $tb = ['B','L'];
        foreach($tb as $tk){
            $smallX = "small$tk"; $largeX = "large$tk"; 
            $betX = "bet$tk"; $intbX = "intb$tk";
            $vN = is_numeric($vdefs[$tk]) ? intval($vdefs[$tk]) : 0;
            //
            if(!empty($cfg[$intbX])){ // intbB='50,150'
                return strpos('(,'.$cfg[$intbX].',)',",$vN,")>0 ? 0 : 1;
            }
            //
            $smallN = empty($cfg[$smallX]) ? 0 : intval($cfg[$smallX]); // 79以下
            $largeN = empty($cfg[$largeX]) ? 0 : intval($cfg[$largeX]); // 101以上
            $bStr = empty($cfg[$betX]) ? '0-0' : $cfg[$betX];     // 80-100
            $bArr = explode('-', "$bStr-"); $b1 = intval($bArr[0]); $b2 = intval($bArr[1]);
            //
            if($smallN>0 && $vN>$smallN){ return 1; } // 79以下
            if($largeN>0 && $vN<$largeN){ return 1; } // 101以上
            if($b1*$b2>0 && ($vN<$b1||$vN>$b2)){ return 1; }
        }
        return 0;
    }

    // 按规则替换一个编码
    static function itmCode(&$cfg, $vdefs, $xhcfg=[]){
        if(empty($cfg['code'])){ return ''; } // 电机-无code
        $code = $cfg['code'];
        $ktb = explode(',','12,13,14,23,24,34,1,2,3,4');
        $tb = ['Pow','Vol','Spec','Jsb1']; foreach($tb as $tk){ $$tk = $vdefs[$tk]; } 
        $vtb = explode(',',"{$Pow}_$Vol,{$Pow}_$Spec,{$Pow}_$Jsb1,{$Vol}_$Spec,{$Vol}_$Jsb1,{$Spec}_$Jsb1,$Pow,$Vol,$Spec,$Jsb1");
        foreach($ktb as $k1=>$v1){
            $ins = empty($cfg["in$v1"]) ? '' : $cfg["in$v1"];
            if(!$ins){ continue; }
            if(!strpos("($ins)","/{$vtb[$k1]}/")){ return 'skip'; }
            $tbv = empty($cfg["tb{$v1}_{$vtb[$k1]}"]) ? '' : $cfg["tb{$v1}_{$vtb[$k1]}"]; 
            if($tbv!=''){ 
                $code = str_replace("{tb{$v1}}", $tbv, $code);
            } 
        } //echo "$code<br>\n";
        $tb = ['B','L'];
        foreach($tb as $tk){
            $code = str_replace("{v$tk}", $vdefs[$tk], $code);
            $tbv = empty($cfg["tb$tk$vdefs[$tk]"]) ? '' : $cfg["tb$tk$vdefs[$tk]"];
            if(!empty($tbv)){ $code = str_replace("{tb$tk}", $tbv, $code); }
        }
        if($code!=$cfg['code']){$cfg['code']=$code; }
        return $code;
    }

    // 一个BOM表List
    static function items(&$data){
        extract($data); // row, rex, vdefs, # xhrow, xhcfg, motc1
        $lists = []; $jsexdo = ''; $rid=0; // jsexdo:额外执行的js
        $cnt = empty($row['数量']) ? 1 : $row['数量']; 
        $items = $xhcfg['items']; $cbc = $cbe = 0; 
        foreach($items as $sk=>$secs){ 
            if($sk=='_Xxx'){ continue; }
            $lists[$rid] = ['no'=>'0','编码'=>'{sec}','名称'=>$xhcfg['itsec'][$sk]]; 
            $no = 0; $rid++;
            foreach($secs as $ik=>$cfg){ 
                $iname = empty($cfg['name']) ? '' : $cfg['name']; if(!$iname){ continue; }
                $ifrom = empty($cfg['from']) ? '' : $cfg['from']; 
                if('skip' == $icode=self::itmCode($cfg, $vdefs, $xhcfg)){ continue; }
                if(self::skipBL($cfg, $vdefs)){ continue; }
                // 
                $itm = []; $ch2 = $ifrom ? substr($ifrom,0,2) : '-';
                if($ifrom && strpos("/fn/fx/",$ch2)>0 && method_exists('bozBom',$ifrom)){ 
                    $itm = self::$ifrom($cfg, $vdefs, $motc1, $xhcfg, $row); 
                    self::fixBodd($itm, $ifrom, $cfg, $vdefs, $motc1, $xhcfg, $row); // 修正B值
                }elseif($ifrom=='db0'){
                    $itm = self::itmDb($icode, $iname); // $cfg['code'] = $icode;
                }else{ // 
                    $itm = ['编码'=>$icode,'名称'=>$iname]; 
                } 
                if(!empty($itm['编码']) && $itm['编码']=='skip'){ continue; }
                $no++; self::itmFix($itm, $no, $cfg);
                // 成本
                $itm['sum'] = $sum = $cnt * $itm['cnt'];
                $icb = $itm['单价'] * $itm['cnt']; //$sum;
                if(strpos("/G/H/",substr($itm['编码'],0,1))>0){
                    $cbe += $icb;
                }else{
                    $cbc += $icb;
                } 
                // 处理合并(TODO)
                if($rid>0 && $itm['编码']==$lists[$rid-1]['编码'] && $itm['规格图号']==$lists[$rid-1]['规格图号']){
                    $lists[$rid-1]['cnt'] += $itm['cnt']; 
                    $no--; continue; 
                }
                if(!empty($itm['jsexdo'])){ $jsexdo .= "\n$itm[jsexdo];"; }
                $lists[$rid] = $itm; $rid++;
            }
        }
        $row['成本C'] = $cbc; $row['成本E'] = $cbe; $row['成本'] = $cbc+$cbe; 
        $row['bozNo'] = self::assBno($row, $vdefs, $xhrow, $xhcfg, $motc1); 
        $row['备注'] = self::assTip1($row, $vdefs, $xhrow, $xhcfg, $motc1); //dump($row);
        $data['row'] = $row; $data['lists'] = $lists; $data['jsexdo'] = $jsexdo; 
    }

    // fixBodd: [整100:-100,-200]; [非100整除:-10的余数,-100的余数]; 
    static function fixBodd(&$itm, $ifrom, $cfg, $vdefs, $motc1, $xhcfg, $row){ 
        if(!empty($itm['tip']) && strlen($itm['编码'])==2 && $itm['备注']=='请添加物料!!'){ 
            $yub = $vdefs['B'] % 100;
            $tbs = $yub ? [$vdefs['B'] % 10, $yub, 100 + $yub] : [100, 200];
            foreach($tbs as $dif){ // .($dk+1)
                $vdNew = $vdefs; $bNew = $vdNew['B'] -= $dif; // B1,B2,B3
                if(!$dif || $bNew<20){ continue; }
                $ifix = self::$ifrom($cfg, $vdNew, $motc1, $xhcfg, $row); 
                if(empty($ifix['tip'])){
                    foreach(['编码','名称','材料','表面处理'] as $tk){ $itm[$tk] = $ifix[$tk]; }
                    if(isset($ifix['cnt']) && !isset($itm['cnt'])){ $itm['cnt']=$ifix['cnt']; }
                    $itm['编码'] .= '-B'; $itm['库存数量'] = 0; $itm['备注'] = "非标"; $itm['bNew'] = $bNew; 
                    unset($itm['tip']); return;
                }
            }
        }
        //return $itm;
    }

    # =================================================================

    // 组型号: BQT01 -B150 - L600 - 25 - SA200 - INV - 18 - H - C - MB3
    static function assBno($row, $vdefs, $xhrow, $xhcfg, $motc1){
        $v = $vdefs; $pid = uval('pid');
        $Pow = str_replace('DC', '', $v['Pow']);
        $no = "$pid-B$v[B]-L$v[L]-$v[Pow]-$v[Vol]-$v[Spec]-$v[Jsb1]-$v[Belt]-$v[Brand]^";
        $no .= (empty($v['Xxj']) || $v['Xxj']=='(无)' || empty($v['Xxb']) || $v['Xxb']=='(无)') ? '' : "-$v[Xxj]-$v[Xxb]"; // 减速比+减速机
        $no .= (empty($v['Fix']) ? '' : "-$v[Fix]".($v['Fix']=='MC' ? $v['Mcmm'] : '')) . (empty($v['Tran']) ? '' : "-$v[Tran]");
        $no .= empty($v['Luomu']) ? '' : "-".$xhcfg['prtab']['vLuomu']['spec'].$v['Luomu'];
        $no .= empty($v['Frame']) ? '' : "-$v[Frame]Z$v[Frhmm]";
        $no .= (empty($v['Welt'])  || $v['Welt']=='(无)') ? '' : "-$v[Welt]";
        $no = str_replace('^', strlen($no)>72 ? '<br>':'', $no);
        return $no;
    }

    // 1.调速电机(台制), 功率:200W, 速比:15K；
    // 2.最大负载100KG,线速度使用范围4-8.5m/min；
    // 3.配红色亚光面PVC平皮带；
    // 4.电机【反装】/电机【MC位移150】。2.皮带【反向】输送；
    // 5.置入【MB2】方形螺母。
    static function assTip1($row, $vdefs, $xhrow, $xhcfg, $motc1){
        $v = $vdefs; $pid = uval('pid');
        $Pow = str_replace('DC', '', $v['Pow']);
        // 1. 定速电机(台邦),功率25W,速比12.5K;
        $s1br = empty($motc1['Brand']['tab'][$v['Brand']]) ? '(未配置)' : $motc1['Brand']['tab'][$v['Brand']];
        if(strpos($v['Pow'],'DC')>0){
            $s1Type = "直流无刷调速";
            $s1cd = "功率{$Pow}W,速比{$v['Jsb1']}K";
        }elseif(strpos("(/57/86/)","/$v[Pow]/")>0){
            $s1Type = '步进';
            $s1cd = "扭矩$v[Spec],{$v['Jsb1']}控制";
        }elseif(strpos("(/MH/MS/)","/$v[Pow]/")>0){
            $s1Type = '伺服';
            $s1cd = "功率$v[Spec],{$v['Jsb1']}控制";
        }else{
            $s1Type = $motc1['dict'][$v['Spec']];
            $s1cd = "功率{$Pow}W,速比$v[Jsb1]K";
        }
        $s1 = "1. {$s1Type}电机($s1br),$s1cd; ";
        // 2. 最大负载100KG,线速度使用范围4-8.5m/min;
        $D = $xhcfg['prtab']['vBelt']['D']; 
        $trate = $xhcfg['prtab']['vBelt']['trate']; 
        $s2 = "2. 参考负载{$xhrow['负载']},线速度参考".self::assSpeed($v['Jsb1'],$D,$trate)."; ";
        // 3. 配红色亚光面PVC平皮带;
        $brow = Dbop::data('store_main', "`类别`='F4' AND `适用机型`='$v[Belt]'", '1', '', 'erp');
        if(!empty($brow['kid'])){ 
            $s3 = "3. 配 {$brow['表面处理']} 平皮带; "; // {$brow['uat']}
        }else{
            $s3 = "3. 配 $v[Belt] 平皮带; ";
        }
        // 4. 电机【反装】/电机【MC位移150】,皮带【反向】输送;
        $vFix = $v['Fix']; $vTran = $v['Tran']; 
        if(!empty($v['Mcmm']) && $vFix=='MC'){
            $s4 = "4. 电机【MC位移{$v['Mcmm']}】,";
        }elseif($vFix=='FZ'){
            $s4 = "4. 电机【反装】,";
        }else{
            $s4 = "4. 电机【默认安装】,";
        }
        if($vTran=='FX'){
            $s4 .= "皮带【反向】输送; ";
        }elseif($vTran=='SX'){
            $s4 .= "皮带【正+反-双向】输送; ";
        }else{
            $s4 .= "皮带【正向】输送; ";
        } 
        // 5. 置入【MB2】方形螺母。 //If fMe.nowMode = "offer" Then s5 = "."
        $spmsg = empty($xhcfg['prtab']['vLuomu']['spmsg']) ? '' : $xhcfg['prtab']['vLuomu']['spmsg']; 
        $spnum = empty($xhcfg['prtab']['vLuomu']['spnum']) ? 0 : $xhcfg['prtab']['vLuomu']['spnum']; 
        if(!empty($v['Luomu'])){
            if($spmsg=='' && intval($spnum)>0){
                $spmsg = "按标配型号打包附赠【" . ($v['Luomu'] * $spnum) . "pcs】螺母";
            }elseif($spmsg==''){
                $spmsg = "每条槽按标配型号置入【" . $v['Luomu'] . "pcs】螺母";
            }
            $s5 = " 5. $spmsg.";
        }else{
            $s5 = " 5. 【标配螺母】.";
        }
        // 
        return "$s1$s2$s3$s4$s5";
    }

    // 线速度
    static function assSpeed($Jsb1, $D, $trate){
        $D = is_numeric($D) ? intval($D) : 0;
        $Jsb1 = is_numeric($Jsb1) ? intval($Jsb1) : 0;
        $trate = is_numeric($trate) ? intval($trate) : 0;
        if(!$D || !$Jsb1 || !$trate){ return '{暂无}'; }
        $res = ($D * 3.14159 * 1350 * $trate) / (1000 * $Jsb1);
        return "(".round($res * 0.6, 1)."~". round($res, 1).") m/min";
    }

    // 得到系列码: [BQZ01]-B150-L1200-...
    static function getProcd($pids){
        if(strlen($pids)<12){ return $pids; } // BTA01-B10
        $tmp = explode('-', $pids);
        return $tmp[0]; // [BTA~BTE]BTA01-B20-B100-L500-25-TA220-SCM-12.5-R1-G
    }

    // 分解参数:parTabkv
    static function parTabkv($parPack, $key=''){
        parse_str(str_replace(';', '&', $parPack), $tabkv);
        if($key){
            return isset($tabkv[$key]) ? $tabkv[$key] : '';
        }else{
            return empty($tabkv) ? [] : $tabkv;
        }
    }
    // 算体积
    static function getVol($pid, $parPack, $rexp=''){
        $pid = self::getProcd($pid);
        $cfg = bozErp::bzcset($pid, 'Sizes'); // ['L'=>50, 'W'=>50, 'H'=>300],
        if(empty($cfg)){ $cfg = bozErp::bzcset('_def','Sizes'); }
        $tkv = self::parTabkv($parPack);
        $gap = bozErp::bzcset('_gap','Sizes'); // 20
        $L = $gap + (empty($tkv['L']) ? 0 : intval($tkv['L']) + $cfg['L']);
        $W = $gap + (empty($tkv['B']) ? 0 : intval($tkv['B']) + $cfg['W']);
        $H = $gap +                                             $cfg['H'];
        if($rexp){ return "$L * $W * $H"; }
        $res = ($L * $W * $H) / 1000**3;
        return round($res,3);
    }
    // 算包装表面积
    static function getSqm($pid, $parPack, $rexp=''){
        $pid = self::getProcd($pid);
        $cfg = bozErp::bzcset($pid, 'Sizes'); // ['L'=>50, 'W'=>50, 'H'=>300],
        if(empty($cfg)){ $cfg = bozErp::bzcset('_def','Sizes'); }
        $tkv = self::parTabkv($parPack);
        $gap = bozErp::bzcset('_gap','Sizes'); // 20
        $L = $gap + (empty($tkv['L']) ? 0 : intval($tkv['L']) + $cfg['L']);
        $W = $gap + (empty($tkv['B']) ? 0 : intval($tkv['B']) + $cfg['W']);
        $H = $gap +                                             $cfg['H'];
        if($rexp){ 
            return $rexp=='1' ? "$L * $W * $H" : "2 * ($L * $W + $L * $H + $W * $H) / 1000^2"; 
        }
        $res = 2 * ($L * $W + $L * $H + $W * $H) / 1000**2;
        return round($res,3);
    }
}
